import numpy as np # 矩阵操作
import pandas as pd # SQL数据处理
from sklearn.preprocessing import StandardScaler
from sklearn.preprocessing import MinMaxScaler

df = pd.read_csv("boston_housing.csv")

# 数据基本信息
# df.info()

# 删除y大于等于50的样本（保留小于50的样本）
# df = df[df.MEDV < 50]
# print(df.shape)

# 从原始数据中分离输入特征x和输出y
y = df["MEDV"]
x = df.drop("MEDV", axis = 1)

# 尝试对y（房屋价格）做log变换，对log变换后的价格进行估计
log_y = np.log1p(y)

# RAD的含义是距离高速公路的便利指数。虽然给的数值是数值型，但实际是索引，可换成离散特征/类别型特征编码试试。
x["RAD"].astype("object")
X_cat = x["RAD"]
X_cat = pd.get_dummies(X_cat, prefix="RAD")

x = x.drop("RAD", axis = 1)
#特征名称，用于保存特征工程结果
feat_names = x.columns

# print(X_cat.head())

# 数值特征标准化

# 分别初始化对特征和目标值的标准化器
# ss_X = StandardScaler()
# ss_y = StandardScaler()
ss_X = MinMaxScaler()
ss_y = MinMaxScaler()

# ss_log_y = StandardScaler()
ss_log_y = MinMaxScaler()

# 分别对训练和测试数据的特征以及目标值进行标准化处理
# 对训练数据，先调用fit方法训练模型，得到模型参数；然后对训练数据和测试数据进行transform
x = ss_X.fit_transform(x)

#对y做标准化不是必须
#对y标准化的好处是不同问题的w差异不太大，同时正则参数的范围也有限
# y = ss_y.fit_transform(y.reshape(-1, 1))
# log_y = ss_y.fit_transform(log_y.reshape(-1, 1))

fe_data = pd.DataFrame(data = x, columns = feat_names, index = df.index)
fe_data = pd.concat([fe_data, X_cat], axis = 1, ignore_index=False)

#加上标签y
fe_data["MEDV"] = y
fe_data["log_MEDV"] = log_y

#保存结果到文件
fe_data.to_csv('FE_boston_housing.csv', index=False)
